﻿using ScanSnap.Domain;
using ScanSnap.Domain.JSON;
using ScanSnap.Util;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;

using System.Threading.Tasks;
using System.Windows.Media.Animation;
using System.Collections;
using System.Globalization;
using System.Threading;

namespace ScanSnap.Wpf.WpfWindow
{
    /// <summary>
    /// Interaction logic for ModelWindow.xaml
    /// </summary>
    public partial class MainApplicationWindow : Window
    {
        private static MainApplicationWindow instance;

        private enum MessageType {CLEAR, ERROR, INFO}
        public List<Document> DocumentNameList { get; set; }
        public List<Document> DocumentNameSearchList { get; set; }
        public List<Tag> TagList { get; set; }
        public List<Tag> CustomTagList { get; set; }
        public List<Tag> TagSearchList { get; set; }
        public List<Tag> CustomTagSearchList { get; set; }
        public int DefaultIndex { get; set; }
        public List<Organization> Organizations { get; set; }
        public List<FileEntry> PdfFileList { get; set; }
        public int NumberOfFiles { get; set; }
        public List<Patient> PatientList { get; set; }
        public List<DocumentType> DocumentTypeList { get; set; }
        public List<DocumentType> DocumentTypeSearchList { get; set; }
        private bool reloadTags = true;

        public readonly string INVALID_ID = "選択してください";
        private readonly static int REFRESH_RATE = 10;  //senconds
        System.Windows.Threading.DispatcherTimer dispatcherTimer;

        public List<string> ErrorList { set; get; }

        private Organization org = new Organization();
        private User user;
        private bool isClosed = false;

        enum PERIOD { YEAR, MONTH, WEEK, DATE };

        private MainApplicationWindow(User user)
        {
            InitializeComponent();
            UpdateDatePickerDateFormat();
            this.user = user;
            SetProfile();
            LoadOrganizations();
            LoadDocumentType();

            NumberOfFiles = 0;
            PdfFileList = null;
            LoadPdfFileList();
            //PdfGrabTimerStart();
        }

        private void UpdateDatePickerDateFormat()
        {
            CultureInfo ci = CultureInfo.CreateSpecificCulture(CultureInfo.CurrentCulture.Name); 
            ci.DateTimeFormat.ShortDatePattern = "yyyy/MM/dd"; 
            Thread.CurrentThread.CurrentCulture = ci;
        }

        public static MainApplicationWindow Instance(User user)
        {
            if (MainApplicationWindow.instance == null || !instance.IsActive)
            {
                instance = new MainApplicationWindow(user);
            }

            return instance;
        }

        private void SetProfile()
        {
            FirstNameText.Content = this.user.FirstName;
            LastNameText.Content = this.user.LastName;
        }

        private void LoadOrganizations()
        {
            string userId = user.Id;

            try
            {
                this.Organizations = JsonService.OrgnizationsByUseridJSON(userId);
                if (this.Organizations != null)
                {
                    ComboOrganizationName.ItemsSource = Organizations;
                    ComboOrganizationSearchName.ItemsSource = Organizations;
                }
                else
                    SetMessage(ErrorMessage.ORGANIZATION_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }
        }

        public void LoadDocumentType()
        {
           try
           {
               DocumentTypeList = JsonService.DocumentTypes();
               
               if (DocumentTypeList != null)
               {
                   DocumentTypeSearchList = DocumentTypeList;
                   ComboDocumentType.ItemsSource = DocumentTypeList;
                   ComboDocumentTypeSearch.ItemsSource = DocumentTypeSearchList;
               }
               else
                   SetMessage(ErrorMessage.DOCUMENT_TYPE_LIST_LOADING_ERROR, MessageType.ERROR);
           }
           catch(WebException)
           {
               SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
           }
        }

        public void LoadDocumentNames(String documentTypeId)
        {
            try
            {
                this.DocumentNameList = JsonService.DocumentNames(documentTypeId);
                if (this.DocumentNameList != null)
                {
                    ComboDocumentName.ItemsSource = this.DocumentNameList;
                    ComboDocumentName.SelectedIndex = 0;
                }
                else
                    SetMessage(ErrorMessage.DOCUMENT_NAME_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }
        }

        public void LoadDocumentNamesSearch(String documentTypeId)
        {
            try
            {
                List<Document> list = JsonService.DocumentNames(documentTypeId);
                list.RemoveAt(0);
                this.DocumentNameSearchList = list;
                if (this.DocumentNameSearchList != null)
                {
                    ListViewDocumentNames.ItemsSource = this.DocumentNameSearchList;
                }
                else
                    SetMessage(ErrorMessage.DOCUMENT_NAME_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }
        }

        public void LoadTags(string organizationId ,string documentNameId)
        {
            TagJSON tagJson;
            try
            {
                tagJson = JsonService.TagsAndCustomTags(organizationId, documentNameId);
                if (tagJson != null)
                {
                    TagList = tagJson.DocumentTags;
                    CustomTagList = tagJson.CustomTags;
                    ListViewDocumentTag.ItemsSource = TagList;
                    ListViewDocumentCustomTag.ItemsSource = CustomTagList;
                }
                else
                    SetMessage(ErrorMessage.TAG_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }
        }

        public void LoadSearchTags(string organizationId, string documentNameId)
        {
            TagJSON tagJson;
            try
            {
                tagJson = JsonService.TagsAndCustomTags(organizationId, documentNameId);
                if (tagJson != null)
                {
                    TagSearchList = tagJson.DocumentTags;
                    CustomTagSearchList = tagJson.CustomTags;
                    ListViewDocumentSearchTag.ItemsSource = TagSearchList;
                    ListViewDocumentSearchCustomTag.ItemsSource = CustomTagSearchList;
                }
                else
                    SetMessage(ErrorMessage.TAG_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }
        }

        public void LoadSearchTags_2(string organizationId, IList documentIdList)
        {
            TagJSON tagJson;
            try
            {
                tagJson = JsonService.TagsAndCustomTagsList(organizationId, documentIdList);
                if (tagJson != null)
                {
                    TagSearchList = tagJson.DocumentTags;
                    CustomTagSearchList = tagJson.CustomTags;
                    ListViewDocumentSearchTag.ItemsSource = TagSearchList;
                    ListViewDocumentSearchCustomTag.ItemsSource = CustomTagSearchList;
                }
                else
                    SetMessage(ErrorMessage.TAG_LIST_LOADING_ERROR, MessageType.ERROR);
            }
            catch (WebException)
            {
                SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            }


            //TagJSON tagJson;
            //try
            //{
            //    tagJson = JsonService.TagsAndCustomTags_2(organizationId);
            //    if (tagJson != null)
            //    {
            //        TagSearchList = tagJson.DocumentTags;
            //        CustomTagSearchList = tagJson.CustomTags;
            //        ListViewDocumentSearchTag.ItemsSource = TagSearchList;
            //        ListViewDocumentSearchCustomTag.ItemsSource = CustomTagSearchList;
            //    }
            //    else
            //        SetMessage(ErrorMessage.TAG_LIST_LOADING_ERROR, MessageType.ERROR);
            //}
            //catch (WebException)
            //{
            //    SetMessage(ErrorMessage.SERVER_CONNECT_ERROR, MessageType.ERROR);
            //}

        }

        private void PdfGrabTimerStart()
        {
            dispatcherTimer = new System.Windows.Threading.DispatcherTimer();
            dispatcherTimer.Tick += new EventHandler(dispatcherTimer_Tick);
            dispatcherTimer.Interval = new TimeSpan(0, 0, REFRESH_RATE);
            dispatcherTimer.Start();
            dispatcherTimer.IsEnabled = true;
        }

        private void PdfGrabTimerStop()
        {
            if (dispatcherTimer != null)
            {
                dispatcherTimer.IsEnabled = false;
                dispatcherTimer.Stop();
            }
        }

        private void dispatcherTimer_Tick(object sender, EventArgs e)
        {
            LoadPdfFileList();
        }

        public void refreshPdfFileList()
        {
            PdfGrabTimerStop();
            LoadPdfFileList();
            PdfGrabTimerStart();
        }


        private void LoadPdfFileList()
        {
            //ListViewFile.Items.Refresh();
            //ListViewFile.InvalidateProperty(ListView.ItemsSourceProperty);

            string pdfPath = ApplicationSettings.SCAN_FOLDER;
            DirectoryInfo info = new DirectoryInfo(@pdfPath);

            if (!Directory.Exists(@pdfPath))
            {
                ErrorList = new List<string>();
                ErrorList.Add("Scansnap folder configuration error" + Environment.NewLine + 
                    "please configure Scansnap.exe.config file" + Environment.NewLine + 
                    @pdfPath + " folder may not exist");
                if (dispatcherTimer != null && dispatcherTimer.IsEnabled)
                {
                    dispatcherTimer.Stop();
                    dispatcherTimer.IsEnabled = false;
                }
                ErrorWindow ew = new ErrorWindow(ErrorList);
                ew.Visibility = System.Windows.Visibility.Visible;
                return;
            }

            List<FileInfo> list = info.GetFiles("*.pdf").OrderByDescending(p => p.CreationTime).ToList();

            PdfFileList = new List<FileEntry>();
            //else
              //  PdfFileList.Clear();
            FileEntry fe;
            foreach(FileInfo f in list) {
                fe = new FileEntry { Name = f.Name, FullName = f.FullName, DateCreated = f.CreationTime.ToString(), IsSelected = false, ReadOnly = f.IsReadOnly };
               
                if(PdfFileList.Contains(fe) == false)
                    PdfFileList.Add(fe);
            }

            if (PdfFileList != null && ListViewFile.Items.Count != 0)
            {

                List<FileEntry> NewPdfFileList = new List<FileEntry>();
                FileEntry fileTemp = null;
                Boolean isselected = false;

                foreach (FileEntry oldfe in ListViewFile.Items)
                {
                    if (oldfe.IsSelected == true)
                    {
                        fileTemp = oldfe;
                        isselected = true;
                        break;
                    }                    
                }

                if (isselected)
                {
                    foreach (FileEntry newfe in PdfFileList)
                    {
                        if (fileTemp != null && newfe.Name.Equals(fileTemp.Name))
                        {
                            newfe.IsSelected = true;
                        }
                        NewPdfFileList.Add(newfe);
                    }

                    PdfFileList = NewPdfFileList;
                }
            }

            ListViewFile.ItemsSource = PdfFileList;
            ListViewFile.Items.Refresh();
        }


        private void SetMessage(string message, MessageType type)
        {
           
                SetLabelMessage(message, type, TextErrorMessage);
            //}));
        }

        private void SetMessage2(string message, MessageType type)
        {
            SetLabelMessage(message, type, TextErrorMessage2);
        }

        private void SetLabelMessage(string message, MessageType type, Label l)
        {
            switch (type)
            {
                case MessageType.CLEAR:
                    l.Content = "";
                    l.Style = (Style)FindResource("MessageLabel");
                    break;
                case MessageType.ERROR:
                    l.Content = message;
                    l.Style = (Style)FindResource("ErrorLabel");
                    break;
                case MessageType.INFO:
                    l.Content = message;
                    l.Style = (Style)FindResource("MessageLabel");
                    break;
            }
        }

        private void ValidateButtonFormSubmit()
        {
            ErrorList = new List<string>();

            if (ComboOrganizationName.SelectedIndex == 0)
            {
                ErrorList.Add("事業所IDを入力してください  / Please Select Organization");
            }

            if (ComboDocumentType.SelectedIndex == 0)
                ErrorList.Add("事業所IDを入力してください  / Please Select Document Type");

            if (ComboDocumentName.SelectedIndex == 0)
                ErrorList.Add("事業所IDを入力してください / Please selet Master Document Name");

            if(RadioAttachmentNo.IsChecked == false && RadioAttachmentYes.IsChecked == false)
                ErrorList.Add("添付書類の有無を選択してください / Please Define Attachement Properties");

            /*
             * 
             * 
             * 
            if (RadioPdfDateNo.IsChecked == false && RadioPdfDateYes.IsChecked == false)
                ErrorList.Add("保存期間の指定の有無を選択してください RadioPdfDateNo");

            if (RadioRetentionPeriodNo.IsChecked == false && RadioRetentionPeriodYes.IsChecked == false)
                ErrorList.Add("書類の日付の有無を選択してください RadioRetentionPeriodNo");

             * 
             * 
             * */

            if (RadioPdfDateYes.IsChecked == false)
                ErrorList.Add("保存期間の指定の有無を選択してください / Please Define PDF Date");

            if (RadioRetentionPeriodYes.IsChecked == false)
                ErrorList.Add("書類の日付の有無を選択してください / Please Define Retension Data");

            bool hasSelected = false;
            foreach(FileEntry f in PdfFileList) {
                if (f.IsSelected == true)
                {
                    hasSelected = true;
                    break;
                }
            }

            if (ComboDocumentType.SelectedIndex == 2)
            {
                if (ComboPatientName.SelectedIndex == 0)
                {
                    ErrorList.Add("事業所IDを入力してください  / Please Select Patient");
                }
                else if (TextPatientId.Text == "")
                {
                    ErrorList.Add("事業所IDを入力してください  / Please Select Patient");
                }

            }

            if (hasSelected == false)
                ErrorList.Add("書類情報を選択してください / Please Select the File to Upload");

        }

        private void resetUploadForm()
        {
            TextPatientId.Text = "";
            ComboPatientName.SelectedIndex = 0;
            LabelPatientAddress.Content = "";
            LabelPatientDateOfBirth.Content = "";
            LabelPatientSex.Content = "";
            ComboDocumentType.SelectedIndex = 0;
            ComboDocumentName.SelectedIndex = 0;
            ComboOrganizationName.SelectedIndex = 0;
            RadioPdfDateYes.IsChecked = false;
            RadioPdfDateNo.IsChecked = false;
            RadioRetentionPeriodYes.IsChecked = false;
            RadioRetentionPeriodNo.IsChecked = false;
            DatePickerPdfDate.Text = "";
            ComboRetentionPeriodUnit.SelectedValue = "";
            ComboRetentionPeriodValue.SelectedValue = "";

            if (PdfFileList != null) { 
                foreach (FileEntry f in PdfFileList)
                {
                    if (f.IsSelected == true)
                    {
                        f.IsSelected = false;
                    }
                }
            }
        }

        private void AddDocumentTypesForPatient(ref Patient bdt)
        {
            if(bdt.DocumentTypes != null)
                bdt.DocumentTypes.Clear();

        }

        private void SubmitValidation()
        {
            ErrorList = new List<string>();

            string organizationId = TextOrganizationSearchId.Text;
            if (organizationId.Length != 3)
            {
                ErrorList.Add("事業所名を選択してください");
                ErrorList.Add("事業所IDを入力してください");
            }

            if (CategoryA.IsChecked == false && CategoryB.IsChecked == false && CategoryC.IsChecked == false)
            {
                ErrorList.Add("書類タイプを選択してください");
            }

            /*
            bool hasSelected = false;

            
            foreach (BoolStringClass b in TagList)
            {
                if (b.Selected == true)
                {
                    hasSelected = true;
                    break;
                }
            }
             

            if (hasSelected == false)
            {
                ErrorList.Add("書類名を選択してください");
            }
            */

        }

        private void SubmitSearchValidation()
        {
            ErrorList = new List<string>();
            
            if (ComboOrganizationSearchName.SelectedIndex == 0)
            {
                ErrorList.Add("Please select the Organization");
            }

            if (ComboDocumentTypeSearch.SelectedIndex == 0)
            {
                ErrorList.Add("Please select the Document Type");

            }
            else
            {
                DocumentType docType = (DocumentType)ComboDocumentTypeSearch.SelectedItem;
                if (docType.Name.StartsWith("B"))
                {
                    if(ComboPatientSearchName.SelectedIndex == 0)
                    {
                        ErrorList.Add("Please select the Patient");
                    }
                       
                }

            }
            if(ListViewDocumentNames.SelectedItems.Count == 0)
            {
                ErrorList.Add("Please select Document Names");
            }
            try
            {
                DateTime startD = DatePickerRangeStartDate.SelectedDate.Value;
                Debug.WriteLine("The startDate Value is " + startD);
                //DateTime endD = DatePickerRangeEndDate.SelectedDate.Value;
                //Debug.WriteLine("The date endDate is " + endD);
                //Debug.WriteLine("Comparison  "+endD.CompareTo(startD));
                //if (endD.CompareTo(startD) == -1)
                //{
                    //ErrorList.Add("Please Select Correct Date Values");
                //}


            }
            catch (InvalidOperationException ex)
            {
                Debug.WriteLine("Error occued at The DatePickerRangeStartDate Value is "+ ex.GetType());
                ErrorList.Add("Please Select the Start Date for the Retention Period");
                return;
            }

        }




        private void SetPatientProperties(Patient p)
        {
            if (p != null)
            {
                TextPatientId.Text = p.HcsId;
                ComboPatientName.SelectedItem = p;
                LabelPatientAddress.Content = p.Address;
                LabelPatientDateOfBirth.Content = p.DataOfBirth + " ( " + p.Age + " )";
                LabelPatientSex.Content = p.SexString;
            }
            else
            {
                TextPatientId.Text = "";
                ComboPatientName.SelectedIndex = 0;
                LabelPatientAddress.Content = "";
                LabelPatientDateOfBirth.Content = "";
                LabelPatientSex.Content = "";
            }
        }

        
       
        public void CreateCheckBoxList(int index)
        {
           
            switch (index)
            {
                case 0:
                    SearchPatientComponentView(System.Windows.Visibility.Hidden);
                    break;
                case 1:
                    SearchPatientComponentView(System.Windows.Visibility.Hidden);
                    break;
                case 2:
                    SearchPatientComponentView(System.Windows.Visibility.Visible);
                    break;
                case 3:
                    SearchPatientComponentView(System.Windows.Visibility.Hidden);
                    break;
            }

           if(TagList != null)
            TagList.Clear();
           
        }

        private void BooleanPropertySet(bool state, params UIElement[] elements)
        {
            foreach (UIElement arg in elements)
            {
                arg.IsEnabled = state;
            }
        }

        public Organization ActiveOrganization
        {
            set {
                org = value;
            }
            get
            {
                this.org = Organizations.Find(x => x.Id == TextOrganizationId.Text);
                return this.org;
            }
        }

        private void SearchPatientComponentView(System.Windows.Visibility state)
        {
            LabelSearchPatientEnable.Visibility = state;
            LabelSearchPatientId.Visibility = state;
            LabelSearchPatientName.Visibility = state;
            CheckboxPatientSearch.Visibility = state;
            TextPatientSearchId.Visibility = state;
            ComboPatientSearchName.Visibility = state;
        }


        private Organization FindOrganizationByCode(string code)
        {
            {
                var query = from r in Organizations
                            where r.Code == code
                            select r;

                if (query.ToList().Count > 0)
                {
                    return query.ToList()[0];
                }
                else
                {
                    //exception and logger
                    return null;
                }
            }
        }

        private void ResetOrganizationNotFound()
        {
            ComboOrganizationName.SelectedIndex = 0;
            ComboPatientName.ItemsSource = null;
            TextPatientId.Text = "";
            ClearTags();
        }

        private void ClearTags()
        {
            ListViewDocumentCustomTag.ItemsSource = null;
            ListViewDocumentTag.ItemsSource = null;
            ListViewDocumentCustomTag.Items.Refresh();
            ListViewDocumentTag.Items.Refresh();
            ListViewDocumentCustomTag.Items.Clear();
            ListViewDocumentTag.Items.Clear();
        }

        private void ClearSearchTags()
        {
            ListViewDocumentSearchTag.ItemsSource = null;
            ListViewDocumentSearchCustomTag.ItemsSource = null;
            ListViewDocumentSearchTag.Items.Refresh();
            ListViewDocumentSearchCustomTag.Items.Refresh();
            ListViewDocumentSearchTag.Items.Clear();
            ListViewDocumentSearchCustomTag.Items.Clear();            
        }

        private void doValidate()
        {
        }

        private void TabControl_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            if (e.Source is TabControl)
            {
                if (PDFUploadTab.IsSelected)
                {
                    PdfGrabTimerStart();
                }
                if (PDFViewerTab.IsSelected)
                {
                    PdfGrabTimerStop();
                }
            }
        }

        private void DocumentSelectType_Checked(object sender, RoutedEventArgs e)
        {
            try
            {
                if (Calender.IsChecked == true)
                {
                    ComboRetentionPeriodSearchValue.IsEnabled = false;
                    ComboRetentionPeriodSearchUnit.IsEnabled = false;
                    DatePickerRangeStartDate.IsEnabled = true;
                }
                else if (Unit.IsChecked == true)
                {
                    DatePickerRangeStartDate.IsEnabled = false;
                    ComboRetentionPeriodSearchValue.IsEnabled = true;
                    ComboRetentionPeriodSearchUnit.IsEnabled = true;
                }
            }
            catch (Exception)
            {
            }
        }

        private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            if (isClosed == true)
            {
                Application.Current.Shutdown();
                Environment.Exit(0);
            }
            else
            {
                e.Cancel = true;
            }
        }
    }
}
